package com.atguigu.springcloud.service;

import org.springframework.cloud.openfeign.FeignClient;
import org.springframework.stereotype.Component;
import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.PathVariable;

/**
 * @auther zzyy
 * @create 2020-02-20 11:55
 */

/**
 * fallback = PaymentFallbackService.class 指使用PaymentFallbackService类作为熔断器的fallback类
 * 这里的fallback类必须实现PaymentHystrixService接口，否则会报错
 * 这里的fallback类必须是Spring Bean，否则会报错
 * 这样就可以不用在Controller来实现Hystrix的服务降级了,而是通过实现PaymentFallbackService类来实现。
 */
@Component
@FeignClient(value = "CLOUD-PROVIDER-HYSTRIX-PAYMENT" ,fallback = PaymentFallbackService.class)
public interface PaymentHystrixService
{
    @GetMapping("/payment/hystrix/ok/{id}")
    public String paymentInfo_OK(@PathVariable("id") Integer id);

    @GetMapping("/payment/hystrix/timeout/{id}")
    public String paymentInfo_TimeOut(@PathVariable("id") Integer id);
}

/**
 * OpenFeign 是一个声明式的 Web 服务客户端，它允许你通过接口调用 HTTP API，与服务进行交互。它的底层实现依赖于 Ribbon 进行负载均衡和 RestTemplate 来发送 HTTP 请求。下面是 OpenFeign 的工作流程和实现细节：
 *
 * 1. 定义 Feign Client
 * 在代码中，你使用 @FeignClient 注解来定义一个 Feign 客户端，比如 PaymentFeignService。这个接口的方法将映射到 HTTP 请求。
 *
 * 2. 注解处理
 * Spring 在启动时会扫描带有 @FeignClient 注解的接口，并生成代理类。Feign 会根据接口中的方法签名以及相应的注解（如 @GetMapping）生成对应的 HTTP 请求。
 *
 * 3. 代理实现
 * 当你调用 PaymentFeignService 接口中的方法时，实际上是调用了由 Spring 创建的代理对象。这个代理对象会在幕后进行以下操作：
 *
 * 构建请求：根据接口方法的注解，构建 HTTP 请求，包括 URL、请求方法 (GET、POST 等)、请求体和参数等。
 *
 * 调用 Ribbon：在请求过程中，Feign 与 Ribbon 集成，通过 Ribbon 获取注册在 Eureka 中的服务实例列表，然后选择一个可用实例进行请求。这是通过 @FeignClient 中指定的 value 属性（如 "CLOUD-PAYMENT-SERVICE"）对应的服务名来进行服务发现和负载均衡。
 *
 * 4. 发送请求
 * Feign 使用 RestTemplate 发送 HTTP 请求。具体步骤如下：
 *
 * 将构建好的请求信息传递给 RestTemplate，执行实际的 HTTP 请求。
 * 等待响应并处理结果。
 * 5. 处理响应
 * 接收到响应后，Feign 会根据定义的返回类型（如 CommonResult<Payment>）进行转换。
 * 如果需要，Feign 会将响应体映射到 Java 对象，通常使用 Jackson 或 Gson 来进行 JSON 反序列化。
 * 6. 错误处理
 * 如果 HTTP 请求失败（如超时、4xx/5xx 错误），可以定义 fallback 方法来处理错误。这在 Feign 客户端中是可选的，但在生产环境中非常有用，以提高应用的健壮性。
 * 总结
 * OpenFeign 的核心流程如下：
 *
 * 定义 Feign 接口。
 * Spring 生成代理类并处理注解。
 * 方法调用触发 HTTP 请求的构建。
 * Ribbon 选择服务实例并发送请求。
 * 使用 RestTemplate 执行 HTTP 请求。
 * 接收和处理响应。
 * 通过这种方式，OpenFeign 使得与微服务之间的通信变得简单而优雅，开发者只需关注业务逻辑，而无需处理底层的 HTTP 细节。
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 *
 */
